MAPS

Global Student to Teacher Ratios

World Tile Grid

Photo by Mario Heller on Unsplash

Photo by Mario Heller on Unsplash

I realized if you can change a classroom, you can change a community,
and if you change enough communities you can change the world…
— Erin Gruwell


Ingest

country, year, indicator, measure

df_students <- read.csv("archetypes/student-teacher-ratios/student-teacher-ratios.csv", header = TRUE)
df_students

Ingest

world tile grid

worldtilegrid <- read.csv("archetypes/world-tile-grid.csv", header = TRUE)

df_world_tile <- worldtilegrid %>% 
  mutate(
    alpha.2 = if_else(name == "Namibia", "NA", alpha.2),
    region = if_else(region == "Americas", sub.region, region),
    region = if_else(region %in% c("Northern America", "Central America", "Caribbean"), "North America", region),
    region = if_else(region == "Southern America", "South America", region),
    region = fct_reorder(region, x)
  )

df_world_tile

Wrangle

take latest available measure and merge with tile grid for coordinates

## data merged with tile map
df_students_tile <- df_students %>% 
  group_by(country, indicator) %>% 
  filter(year == max(year)) %>% 
  ungroup() %>% 
  complete(indicator, nesting(country, country_code)) %>% 
  filter(
    indicator %in% c("Primary Education", "Secondary Education", "Tertiary Education"), 
    str_detect(country_code, "[A-Z]")
  ) %>% 
  mutate(alpha.3 = country_code) %>%
  full_join(df_world_tile) %>%
  filter(
    !is.na(indicator),
    !is.na(region)
  ) %>% 
  mutate(alpha.2 = if_else(country == "Namibia", "NA", alpha.2))

df_students_tile <- df_students_tile %>% select(indicator, country, alpha.2, year, student_ratio, x, y)

df_students_tile

Analytics

calculate bins for each indicator

df_pri <- filter(df_students_tile, indicator == "Primary Education")
df_pri$bin <- as.character(as.numeric(cut(df_pri$student_ratio, 5)))
df_pri$bin[is.na(df_pri$bin)] <- "0"

df_sec <- filter(df_students_tile, indicator == "Secondary Education")
df_sec$bin <- as.character(as.numeric(cut(df_sec$student_ratio, 5)))
df_sec$bin[is.na(df_sec$bin)] <- "0"

df_prisec <- rbind(df_pri, df_sec)

df_tert <- filter(df_students_tile, indicator == "Tertiary Education")
df_tert$bin <- as.character(as.numeric(cut(df_tert$student_ratio, 5)))
df_tert$bin[is.na(df_tert$bin)] <- "0"

View

color by bin

theme_opts <- theme(
    text = element_text(family = "inconsolata"), 
    plot.title = element_text(color = "black", size = 14, face = "bold", family = "inconsolata", hjust = 0.5),
    plot.subtitle = element_text(color = "black", size = 12, family = "inconsolata", hjust = 0.5),
    plot.caption = element_text(color = "#555555", size = 8, family = "inconsolata"),    
    plot.margin = margin(10, 10, 10, 10),
    plot.background = element_rect(fill = "#ffffff", color = NA),
    panel.grid.major = element_blank(),
    panel.grid.minor = element_blank(),
    panel.background=element_rect(fill="#ffffff", colour="#ffffff"),
    panel.border = element_blank(),
    axis.text = element_blank(),
    axis.line = element_blank(),
    axis.ticks = element_blank(),
    axis.title = element_blank(),
    strip.background = element_rect(fill = "white", color = "white"),
    strip.text = element_text(color = "black", size = 14, face = "bold", family = "inconsolata", hjust = 0.5)
)

bin_fill_palette <- c(
  "0" = "#f0f0f0",
  "1" = "#80CBC4",
  "2" = "#C5E1A5",
  "3" = "#FFE082",
  "4" = "#FFAB91",
  "5" = "#EF9A9A"
)

bin_color_palette <- c(
  "0" = darken("#f0f0f0", 0.2),
  "1" = darken("#80CBC4", 0.2),
  "2" = darken("#C5E1A5", 0.2),
  "3" = darken("#FFE082", 0.2),
  "4" = darken("#FFAB91", 0.2),
  "5" = darken("#EF9A9A", 0.2)
)

## facetted by prim., sec. and tert. education level
v1 <- ggplot(df_prisec, aes(x = x, y = y, fill = bin, color = bin )) + 
    geom_tile(size = 0.5) +
    geom_text(aes(x = x, y = y, label = alpha.2), color = "black", size = 3, 
              fontface = "bold", family = "inconsolata") +
    scale_fill_manual(values = bin_fill_palette) +
    scale_color_manual(values = bin_color_palette) +
    scale_y_reverse() +
    coord_equal() +
    facet_wrap(~indicator) +
    labs(
      title = "Global student to teacher ratios",
      subtitle = "Latest reported student to teacher ratio per country and educational level (2012-2018)\n",
      caption = NULL, x = NULL, y = NULL) +
    theme_bw() +
    theme_opts +
    theme(legend.position = "none")

v2 <- ggplot(df_prisec, aes(x = x, y = y, fill = bin, color = bin )) + 
    geom_tile(size = 0.5) +
    geom_text(aes(x = x, y = y, label = alpha.2), color = "black", size = 3.5, 
              fontface = "bold", family = "inconsolata") +
    scale_fill_manual(values = bin_fill_palette) +
    scale_color_manual(values = bin_color_palette) +
    scale_y_reverse() +
    coord_equal() +
    labs(
      title = "Tertiary Education",
      subtitle = NULL,
      caption = '\nData: "eAtlas of Teachers" by UNESCO', x = NULL, y = NULL) +
    theme_bw() +
    theme_opts +
    theme(legend.position = "bottom")

girafe(ggobj = v1, width_svg = 16, height_svg = 7.5,
       options = list(opts_sizing(rescale = TRUE, width = 1.0))
)
girafe(ggobj = v2, width_svg = 16, height_svg = 10,
       options = list(opts_sizing(rescale = TRUE, width = 1.0))
)

References

citations for narrative and data sources

  • Data Source: UNESCO, eAtlas of Teachers
  • Visualization: inspired by the work of Cédric Scherer